const { QueryTypes } = require("sequelize");
const sequelize = require("../sequelize");
const shopModel = require("../sequelize/shop");
const shopTypeModel = require("../sequelize/shopType");
const typeModel = require("../sequelize/type");
const { uploadFile } = require("../utils/utils");

const formidable = require("formidable");
const path = require("path");
const fs = require("fs");

// 获取表单数据
const getFormData = req => {
	return new Promise((resolve, reject) => {
		const form = new formidable.IncomingForm();
		form.encoding = "utf-8"; // 编码
		form.keepExtensions = true; // 保留扩展名

		form.parse(req, (err, fields, files) => {
			if (err) {
				reject(err);
				return;
			}
			resolve(fields);
		});
	});
};

class Service {
	async list() {
		return {
			code: 200,
			message: "ok",
			result: await shopModel.findAll({
				include: [
					{
						model: shopTypeModel,
					},
					{
						model: typeModel,
					},
				],
			}),
		};
	}

	async add(body) {
		await shopModel.create(body);
		return {
			code: 200,
			message: "ok",
			result: body,
		};
	}

	async update(body) {
		try {
			await shopModel.update(body, {
				where: {
					id: body.id,
				},
			});
		} catch (e) {
			console.error(e);
		}
		return {
			code: 200,
			message: "ok",
			result: body,
		};
	}

	async del(body) {
		await shopModel.destroy({
			where: {
				id: body.id,
			},
		});
		return {
			code: 200,
			message: "ok",
			result: body,
		};
	}

	async addShopType(body) {
		await shopTypeModel.create(body);
		return {
			code: 200,
			message: "ok",
			result: body,
		};
	}

	async delShopType(body) {
		await shopTypeModel.destroy({ where: { id: body.id } });
		return {
			code: 200,
			message: "ok",
			result: body,
		};
	}

	async uploadLogo(req) {
		const fileInfo = await uploadFile(req, "/public/");
		const id = req.url.split("?")[1].split("=")[1];
		if (id) {
			await shopModel.update(
				{
					logo: fileInfo,
				},
				{
					where: {
						id,
					},
				}
			);
		}
		return {
			code: 200,
			message: "ok",
			result: {
				url: fileInfo,
			},
		};
	}

	async uploadCover(req) {
		const fileInfo = await uploadFile(req, "/public/");
		const id = req.url.split("?")[1].split("=")[1];
		if (id) {
			await shopModel.update(
				{
					cover: fileInfo,
				},
				{
					where: {
						id,
					},
				}
			);
		}
		return {
			code: 200,
			message: "ok",
			result: {
				url: fileInfo,
			},
		};
	}

	async getShopByType(query) {
		const shops = await sequelize.query(
			`
                SELECT
                    *,(
                        6371 * acos (
                                    cos ( radians(${query.lat}) )
                                    * cos( radians( lat ) )
                                    * cos( radians( lng ) - radians(${query.lng}) )
                                + sin ( radians(${query.lat}) )
                                        * sin( radians( lat ) )
                        )
                    ) AS distance
                FROM shops
                WHERE typeId = ${query.id}
                HAVING distance < 1000000
                ORDER BY distance
                LIMIT 0 , 20;
            `,
			{ type: QueryTypes.SELECT }
		);
		return {
			code: 200,
			message: "ok",
			result: shops.map(ele => {
				return {
					...ele,
					distance: ele.distance.toFixed(1),
				};
			}),
		};
	}

	async getShopById(query) {
		const shops = await shopModel.findOne({
			where: {
				id: query.id,
			},
			include: [
				{
					model: shopTypeModel,
				},
				{
					model: typeModel,
				},
			],
		});
		return {
			code: 200,
			message: "ok",
			result: shops,
		};
	}
}

module.exports = new Service();
